package com.processmanager.service;

import com.processmanager.sdk.ProcessManager;
import com.processmanager.sdk.model.ProcessInfo;
import com.processmanager.sdk.model.ProcessLog;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;

import jakarta.annotation.PostConstruct;
import jakarta.annotation.PreDestroy;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * 进程管理服务
 * 
 * <p>Spring Boot应用层的进程管理服务，集成SDK并提供WebSocket实时推送：</p>
 * <ul>
 *   <li>进程生命周期管理</li>
 *   <li>实时日志推送</li>
 *   <li>进程状态监控</li>
 *   <li>自动清理过期进程</li>
 * </ul>
 * 
 * @author ProcessManager
 * @version 1.0.0
 * @since 2024-01-01
 */
@Service
public class ProcessService {
    
    private static final Logger logger = LoggerFactory.getLogger(ProcessService.class);
    
    private final ProcessManager processManager;
    private final WebSocketService webSocketService;
    
    /**
     * 构造函数
     * 
     * @param webSocketService WebSocket服务
     */
    public ProcessService(WebSocketService webSocketService) {
        this.webSocketService = webSocketService;
        this.processManager = new ProcessManager();
    }
    
    /**
     * 初始化服务
     */
    @PostConstruct
    public void init() {
        // 设置日志回调，用于实时推送日志
        processManager.setLogCallback(this::handleProcessLog);
        logger.info("进程管理服务初始化完成");
    }
    
    /**
     * 销毁服务
     */
    @PreDestroy
    public void destroy() {
        processManager.shutdown();
        logger.info("进程管理服务已关闭");
    }
    
    /**
     * 执行命令
     * 
     * @param command 要执行的命令
     * @param name 进程名称
     * @return 进程ID
     */
    public String executeCommand(String command, String name) {
        String processId = processManager.executeCommand(command, name);
        
        // 推送进程列表更新
        pushProcessListUpdate();
        
        // 推送系统消息
        webSocketService.pushSystemMessage("新进程已启动: " + name);
        
        logger.info("执行命令成功: {} (进程ID: {})", command, processId);
        return processId;
    }
    
    /**
     * 获取进程信息
     * 
     * @param processId 进程ID
     * @return 进程信息
     */
    public ProcessInfo getProcessInfo(String processId) {
        return processManager.getProcessInfo(processId);
    }
    
    /**
     * 获取所有进程信息
     * 
     * @return 所有进程信息
     */
    public Map<String, ProcessInfo> getAllProcesses() {
        return processManager.getAllProcesses();
    }
    
    /**
     * 停止进程
     * 
     * @param processId 进程ID
     * @return 是否成功
     */
    public boolean stopProcess(String processId) {
        boolean success = processManager.stopProcess(processId);
        
        if (success) {
            // 推送进程列表更新
            pushProcessListUpdate();
            
            // 推送系统消息
            ProcessInfo info = getProcessInfo(processId);
            if (info != null) {
                webSocketService.pushSystemMessage("进程已停止: " + info.getName());
            }
            
            logger.info("停止进程成功: {}", processId);
        } else {
            logger.warn("停止进程失败: {}", processId);
        }
        
        return success;
    }
    
    /**
     * 处理进程日志回调
     * 
     * @param log 日志条目
     */
    private void handleProcessLog(ProcessLog log) {
        // 只做日志区推送，不再推送系统消息弹框
        // 如需全局提示可在其他操作中调用pushSystemMessage
    }
    
    /**
     * 推送进程列表更新
     */
    private void pushProcessListUpdate() {
        Map<String, ProcessInfo> processes = getAllProcesses();
        webSocketService.pushProcessListUpdate(processes);
    }
    
    /**
     * 定时清理已停止的进程（每小时执行一次）
     */
    @Scheduled(fixedRate = 3600000) // 1小时
    public void cleanupStoppedProcesses() {
        try {
            processManager.cleanupStoppedProcesses(24 * 3600); // 保留24小时
            logger.info("定时清理已停止的进程完成");
        } catch (Exception e) {
            logger.error("定时清理进程失败: {}", e.getMessage(), e);
        }
    }
    
    /**
     * 推送进程状态更新
     * 
     * @param processId 进程ID
     * @param status 状态
     */
    public void pushProcessStatus(String processId, String status) {
        webSocketService.pushProcessStatus(processId, status);
    }
} 